﻿using System;
using System.Linq;
using System.Windows.Forms;
using LightPersist;
using LightPersist.Storage;
using SmartDeviceExample.Dom;

namespace SmartDeviceExample
{

	public partial class MainForm : Form
	{
		public MainForm()
		{
			LightProfiling.Lap("MainForm created");
			InitializeComponent();
			listBox1.Items.Add("Loading...");
			LightProfiling.Lap("MainForm initialized");
		}

		private void timerStart_Tick(object sender, EventArgs e)
		{
			timerStart.Enabled = false;
			LightProfiling.Lap("MainForm timerStart...");
			Fill();
			Root.Tasks.CollectionChanged += delegate
			                                	{
			                                		Fill();
			                                	};
			LightProfiling.Lap("MainForm timerStart done.");
		}

		private LightPersistContext _db;
		private readonly object _dbCreateSync = new object();

		public LightPersistContext DB
		{
			get
			{
				if(_db==null)
				{
					LightProfiling.Lap("DB: open & lock...");
					lock(_dbCreateSync)
					{
						LightProfiling.Lap("DB: locked");
						if (_db == null)
						{
							LightProfiling.Lap("DB: create storage...");
							var storage = new BinaryStorage();
							LightProfiling.Lap("DB: created");
							storage.Connect("db");
							LightProfiling.Lap("DB: load metainfo...");
							var metainfo = DomMetainfo.Metainfo;
							LightProfiling.Lap("DB: loaded metainfo");
							LightProfiling.Lap("DB: connected, creating context...");
							_db = new LightPersistContext(storage, metainfo);
							LightProfiling.Lap("DB: context created");
						}
					}
					LightProfiling.Lap("DB: ready");
				}
				return _db;
			}
		}

		public Root Root
		{
			get
			{
				LightProfiling.Lap("Root...");
				var root = DB.RootClass<Root>();
				LightProfiling.Lap("Root done");
				return root;
			}
		}

		void Fill()
		{
			LightProfiling.Lap("Fill: start");
			var tasks = Root.Tasks.ToArray();
			LightProfiling.Lap("Fill: tasks retrieved");
			listBox1.Items.Clear();
			foreach (var task in tasks)
			{
				listBox1.Items.Add(task);
			}
			if (listBox1.Items.Count == 0)
			{
				listBox1.Items.Add("(Empty)");
			}
			LightProfiling.Lap("Fill: Filled");
		}

		private static readonly Random _rnd = new Random();

		private void menuItem1_Click(object sender, EventArgs e)
		{
			LightProfiling.Lap("Add: click");
			DB.Execute = delegate
			             	{
									LightProfiling.Lap("Add: in transaction");
									var task = DB.Create<Task>();
									LightProfiling.Lap("Add: task created");
									Root.Tasks.Add(task);
									LightProfiling.Lap("Add: task added");
									task.Subject = "Task " + _rnd.Next(100);
									LightProfiling.Lap("Add: task subject specified");
								};
			LightProfiling.Lap("Add: complete");
		}

		private void menuItemRemove_Click(object sender, EventArgs e)
		{
			var item = listBox1.SelectedItem as Task;
			if (item != null)
			{
				DB.Execute = delegate
				             	{
				             		Root.Tasks.Remove(item);
				             	};
			}
		}

		private void menuItemExit_Click(object sender, EventArgs e)
		{
			Close();
		}
	}
}